﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;

namespace OfficeBusiness.Model
{
    public class BusinessModel : IBusinessModel
    {
        #region IBusinessModel Members


        EventHandler IBusinessModel.DepartmentSelectedEvent
        {
            get
            {
                return this.departmentSelectedEvent;
            }

            set
            {
                this.departmentSelectedEvent = value;
            }
        }

        EventHandler IBusinessModel.EmployeeSelectedEvent
        {
            get
            {
                return this.employeeSelectedEvent;
            }

            set
            {
                this.employeeSelectedEvent = value;
            }
        }

        EventHandler IBusinessModel.ProjectsSelectedEvent
        {
            get
            {
                return this.projectsSelectedEvent;
            }

            set
            {
                this.projectsSelectedEvent = value;
            }
        }

        EventHandler IBusinessModel.WorksSelectedEvent
        {
            get
            {
                return this.worksSelectedEvent;
            }

            set
            {
                this.worksSelectedEvent = value;
            }
        }

        Visibility IBusinessModel.DepartmentVisibility
        {
            get
            {
                return this.departmentVisibility;
            }

            set
            {
                if (value == Visibility.Visible)
                {
                    (this as IBusinessModel).DepartmentSelectedEvent.Invoke(value, null);
                }
                else if (value == Visibility.Collapsed)
                {
                    (this as IBusinessModel).ProjectsSelectedEvent.Invoke(value, null);
                }

                this.departmentVisibility = value;
            }
        }

        Visibility IBusinessModel.EmployeesVisibility
        {
            get
            {
                return this.employeesVisibility;
            }

            set
            {
                if (value == Visibility.Visible)
                {
                    (this as IBusinessModel).EmployeeSelectedEvent.Invoke(value, null);
                }
                else if (value == Visibility.Collapsed)
                {
                    (this as IBusinessModel).WorksSelectedEvent.Invoke(value, null);
                }

                this.employeesVisibility = value;
            }
        }

        #endregion
        #region IBusinessModel Methods

        private EventHandler departmentSelectedEvent;
        private EventHandler employeeSelectedEvent;
        private EventHandler projectsSelectedEvent;
        private EventHandler worksSelectedEvent;
        private Visibility employeesVisibility;
        private Visibility departmentVisibility;
        
        IList<ViewModel.Department> IBusinessModel.GetDepartmentsDetails()
        {
            OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
            var deptDetails = from deptTable in dataContext.Departments select deptTable;
            IList<ViewModel.Department> deptList = new List<ViewModel.Department>();
            foreach (var deptRow in deptDetails)
            {
                ViewModel.Department dept = new ViewModel.Department();
                dept.DepartmentNumber = deptRow.Dept_No;
                dept.DepartmentName = deptRow.Dept_Name;
                dept.Location = deptRow.Location;
                deptList.Add(dept);
            }

            return deptList;
        }

        IList<ViewModel.Employee> IBusinessModel.GetEmployeesDetails()
        {
            OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
            var empDetails = from empTable in dataContext.Employees select empTable;
            IList<ViewModel.Employee> empList = new List<ViewModel.Employee>();
            foreach (var empRow in empDetails)
            {
                ViewModel.Employee emp = new ViewModel.Employee();
                emp.EmployeeNumber = empRow.Emp_No;
                emp.FirstName = empRow.Emp_FName;
                emp.LastName = empRow.Emp_LName;
                emp.DepartmentNumber = empRow.Dept_No;
                empList.Add(emp);
            }

            return empList;
        }

        IList<ViewModel.Project> IBusinessModel.GetProjectsDetails()
        {
            OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
            var projDetails = from projTable in dataContext.Projects select projTable;
            IList<ViewModel.Project> projList = new List<ViewModel.Project>();
            foreach (var projRow in projDetails)
            {
                ViewModel.Project project = new ViewModel.Project();
                project.ProjectNumber = projRow.Project_No;
                project.ProjectName = projRow.Project_Name;
                project.Budget = projRow.Budget;
                projList.Add(project);
            }

            return projList;
        }

        IList<ViewModel.Work> IBusinessModel.GetWorksDetails()
        {
            OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
            var workDetails = from workTable in dataContext.Works select workTable;

            IList<ViewModel.Work> workList = new List<ViewModel.Work>();
            foreach (var workRow in workDetails)
            {
                ViewModel.Work work = new ViewModel.Work();
                work.EmployeeNumber = workRow.Emp_No;
                work.ProjectNumber = workRow.Project_No;
                work.JobName = workRow.Job;
                long ticks = (long)workRow.Enter_Date.Value;
                work.StartDate = new DateTime(ticks).ToLocalTime();
                workList.Add(work);
            }

            return workList;
        }

        bool IBusinessModel.InsetRows<T>(IList<T> rows)
        {
            try
            {
                if (rows != null && rows.Count() > 0)
                {
                    OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
                    if (typeof(T) == typeof(ViewModel.Employee))
                    {
                        foreach (var emp in (IList<ViewModel.Employee>)rows)
                        {
                            Employee employee = new Employee();
                            employee.Dept_No = emp.DepartmentNumber;
                            employee.Emp_No = emp.EmployeeNumber;
                            employee.Emp_FName = emp.FirstName;
                            employee.Emp_LName = emp.LastName;
                            dataContext.Employees.InsertOnSubmit(employee);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Department))
                    {
                        foreach (var dept in (IList<ViewModel.Department>)rows)
                        {
                            Department department = new Department();
                            department.Dept_No = dept.DepartmentNumber;
                            department.Dept_Name = dept.DepartmentName;
                            department.Location = dept.Location;
                            dataContext.Departments.InsertOnSubmit(department);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Project))
                    {
                        foreach (var proj in (IList<ViewModel.Project>)rows)
                        {
                            Project project = new Project();
                            project.Project_No = proj.ProjectNumber;
                            project.Project_Name = proj.ProjectName;
                            project.Budget = proj.Budget;
                            dataContext.Projects.InsertOnSubmit(project);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Work))
                    {
                        foreach (var wrk in (IList<ViewModel.Work>)rows)
                        {
                            Work work = new Work();
                            work.Emp_No = wrk.EmployeeNumber;
                            work.Project_No = wrk.ProjectNumber;
                            work.Job = wrk.JobName;
                            work.Enter_Date = wrk.StartDate.ToUniversalTime().Ticks;
                            dataContext.Works.InsertOnSubmit(work);
                        }
                    }
                    else
                    {
                        return false;
                    }

                    dataContext.SubmitChanges();
                    return true;
                }
                else
                {
                    return false;
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
                return false;
            }
        }

        bool IBusinessModel.DeleteSelectedRow<T>(T row)
        {
            try
            {
                if (row != null)
                {
                    OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
                    if (typeof(T) == typeof(ViewModel.Employee))
                    {
                        ViewModel.Employee empV = (ViewModel.Employee)(object)row;
                        var empDetails = from empTable in dataContext.Employees where empTable.Emp_No == empV.EmployeeNumber select empTable;
                        foreach (var detail in empDetails)
                        {
                            dataContext.Employees.DeleteOnSubmit(detail);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Department))
                    {
                        ViewModel.Department deptV = (ViewModel.Department)(object)row;
                        var deptDetails = from depTable in dataContext.Departments where depTable.Dept_No == deptV.DepartmentNumber select depTable;
                        foreach (var detail in deptDetails)
                        {
                            dataContext.Departments.DeleteOnSubmit(detail);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Project))
                    {
                        ViewModel.Project projV = (ViewModel.Project)(object)row;
                        var projDetails = from projTable in dataContext.Projects where projTable.Project_No == projV.ProjectNumber select projTable;
                        foreach (var detail in projDetails)
                        {
                            dataContext.Projects.DeleteOnSubmit(detail);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Work))
                    {
                        ViewModel.Work workV = (ViewModel.Work)(object)row;
                        var workDetails = from workTable in dataContext.Works where workTable.Emp_No == workV.EmployeeNumber && workTable.Project_No == workV.ProjectNumber select workTable;
                        foreach (var detail in workDetails)
                        {
                            dataContext.Works.DeleteOnSubmit(detail);
                        }
                    }
                    else
                    {
                        return false;
                    }

                    dataContext.SubmitChanges();
                    return true;
                }
                else
                {
                    return false;
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
                return false;
            }
        }

        bool IBusinessModel.UpdateRows<T>(IList<T> rows)
        {
            try
            {
                if (rows != null && rows.Count > 0)
                {
                    OfficeGeneralDataContext dataContext = new OfficeGeneralDataContext();
                    if (typeof(T) == typeof(ViewModel.Employee))
                    {
                        foreach (var emp in (IList<ViewModel.Employee>)rows)
                        {
                            var empDetails = from empTable in dataContext.Employees where empTable.Emp_No == emp.EmployeeNumber select empTable;
                            bool isNotModified = empDetails.ToList().FirstOrDefault(x => x.Dept_No == emp.DepartmentNumber && x.Emp_FName == emp.FirstName && x.Emp_LName == emp.LastName) != null;
                            if (isNotModified)
                            {
                                continue;
                            }

                            foreach (var detail in empDetails)
                            {
                                dataContext.Employees.DeleteOnSubmit(detail);
                            }

                            Employee employee = new Employee();
                            employee.Dept_No = emp.DepartmentNumber;
                            employee.Emp_No = emp.EmployeeNumber;
                            employee.Emp_FName = emp.FirstName;
                            employee.Emp_LName = emp.LastName;
                            dataContext.Employees.InsertOnSubmit(employee);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Department))
                    {
                        foreach (var dept in (IList<ViewModel.Department>)rows)
                        {
                            var deptDetails = from depTable in dataContext.Departments where depTable.Dept_No == dept.DepartmentNumber select depTable;
                            bool isNotModified = deptDetails.ToList().FirstOrDefault(x => x.Dept_Name == dept.DepartmentName && x.Location == dept.Location) != null;
                            if (isNotModified)
                            {
                                continue;
                            }

                            foreach (var detail in deptDetails)
                            {
                                dataContext.Departments.DeleteOnSubmit(detail);
                            }

                            Department department = new Department();
                            department.Dept_No = dept.DepartmentNumber;
                            department.Dept_Name = dept.DepartmentName;
                            department.Location = dept.Location;
                            dataContext.Departments.InsertOnSubmit(department);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Project))
                    {
                        foreach (var proj in (IList<ViewModel.Project>)rows)
                        {
                            var projDetails = from projTable in dataContext.Projects where projTable.Project_No == proj.ProjectNumber select projTable;
                            bool isNotModified = projDetails.ToList().FirstOrDefault(x => x.Project_Name == proj.ProjectName && x.Budget == proj.Budget) != null;
                            if (isNotModified)
                            {
                                continue;
                            }

                            foreach (var detail in projDetails)
                            {
                                dataContext.Projects.DeleteOnSubmit(detail);
                            }

                            Project project = new Project();
                            project.Project_No = proj.ProjectNumber;
                            project.Project_Name = proj.ProjectName;
                            project.Budget = proj.Budget;
                            dataContext.Projects.InsertOnSubmit(project);
                        }
                    }
                    else if (typeof(T) == typeof(ViewModel.Work))
                    {
                        foreach (var wrk in (IList<ViewModel.Work>)rows)
                        {
                            var workDetails = from workTable in dataContext.Works where workTable.Emp_No == wrk.EmployeeNumber && workTable.Project_No == wrk.ProjectNumber select workTable;
                            bool isNotModified = workDetails.ToList().FirstOrDefault(x => x.Job == wrk.JobName && x.Enter_Date == wrk.StartDate.ToUniversalTime().Ticks) != null;
                            if (isNotModified)
                            {
                                continue;
                            }

                            foreach (var detail in workDetails)
                            {
                                dataContext.Works.DeleteOnSubmit(detail);
                            }

                            Work work = new Work();
                            work.Emp_No = wrk.EmployeeNumber;
                            work.Project_No = wrk.ProjectNumber;
                            work.Job = wrk.JobName;
                            work.Enter_Date = wrk.StartDate.ToUniversalTime().Ticks;
                            dataContext.Works.InsertOnSubmit(work);
                        }
                    }
                    else
                    {
                        return false;
                    }

                    dataContext.SubmitChanges();
                    return true;
                }
                else
                {
                    return false;
                }
            }
            catch (Exception ex)
            {
                MessageBox.Show(ex.Message);
                return false;
            }
        }

        #endregion
    }
}
